/**
 * Project Name:dsrs-systemservice-web
 * File Name:WeakPwdController.java
 * Package Name:com.bwda.dsrs.systemservice.controller;
 * Date:2019年4月28日
 * Copyright (c) 2019, 江苏保旺达软件有限公司 All Rights Reserved.
 */
package com.bwda.dsrs.systemservice.controller;

import com.bwda.dsrs.base.centerbase.response.CentreCutPageResponse;
import com.bwda.dsrs.base.centerbase.response.CentreListResponse;
import com.bwda.dsrs.base.centerbase.response.ResponseEntity;
import com.bwda.dsrs.base.util.CopyUtil;
import com.bwda.dsrs.systemservice.annotations.NeedRole;
import com.bwda.dsrs.systemservice.aspect.LogTypeEnum;
import com.bwda.dsrs.systemservice.aspect.Loggable;
import com.bwda.dsrs.systemservice.domain.Constants;
import com.bwda.dsrs.systemservice.domain.condition.datadict.DatadictCondition;
import com.bwda.dsrs.systemservice.domain.exception.SystemServiceException;
import com.bwda.dsrs.systemservice.domain.form.weakpwd.WeakPwdCreateForm;
import com.bwda.dsrs.systemservice.domain.form.weakpwd.WeakPwdQueryForm;
import com.bwda.dsrs.systemservice.domain.form.weakpwd.WeakPwdUpdateForm;
import com.bwda.dsrs.systemservice.domain.po.datadict.DatadictPo;
import com.bwda.dsrs.systemservice.domain.vo.datadict.DatadictVo;
import com.bwda.dsrs.systemservice.service.DatadictService;
import com.bwda.dsrs.systemservice.service.WeakPwdService;
import com.bwda.dsrs.systemservice.utils.ExcelUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.apache.commons.io.FilenameUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.List;

/**
 * 弱密码
 *
 * @author liangjianyong
 * @date 2019/4/11
 */
@RestController
@RequestMapping("/s/weakpwd")
@Api(value = "/s/weakpwd", tags = "弱密码管理")
public class WeakPwdController extends BaseController {

    private final Logger logger = LoggerFactory.getLogger(WeakPwdController.class);

    @Autowired
    private DatadictService datadictService;

    @Autowired
    private WeakPwdService weakPwdService;

    @NeedRole("sysadminrole")
    @ApiOperation(value = "新增弱密码", notes = "新增弱密码", httpMethod = "POST")
    @Loggable(descp = "新增弱密码", type = LogTypeEnum.CREATE, include = "")
    @RequestMapping(value = "/add", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<DatadictVo> add(@ModelAttribute @Valid WeakPwdCreateForm form)
            throws SystemServiceException {
        DatadictPo po = CopyUtil.transfer(form, DatadictPo.class);
        DatadictCondition condition = CopyUtil.transfer(po, DatadictCondition.class);
        if (weakPwdService.selectByvalue(condition) != Constants.WEAKPWDREPEAT) {
            logger.error("已经存在相同的弱密码值,新增弱密码失败");
            return getFailResult("已经存在相同的弱密码值");
        }
        weakPwdService.insert(po);
        DatadictVo vo = CopyUtil.transfer(po, DatadictVo.class);
        return getSuccessResult(vo);
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "查询弱密码", notes = "查询弱密码", httpMethod = "GET")
    @Loggable(descp = "查询弱密码", type = LogTypeEnum.QUERY, include = "")
    @RequestMapping(value = "/query", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<DatadictVo> query(@ApiParam(value = "弱密码ID", required = true) @RequestParam Long dataDictId)
            throws SystemServiceException {
        DatadictPo po = datadictService.queryWithValid(dataDictId);
        DatadictVo vo = CopyUtil.transfer(po, DatadictVo.class);
        return getSuccessResult(vo);
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "查询弱密码(根据CODE查询)", notes = "查询弱密码(根据CODE查询)", httpMethod = "GET")
    @Loggable(descp = "查询弱密码(根据CODE查询)", type = LogTypeEnum.QUERY, include = "")
    @RequestMapping(value = "/queryByCode", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<DatadictVo> queryByCode(
            @ApiParam(value = "弱密码CODE", required = true) @RequestParam String dataDictCode)
            throws SystemServiceException {
        DatadictCondition condition = new DatadictCondition();
        condition.setDelFlag(Constants.NOT_DELETED);
        condition.setDataDictCode(dataDictCode);
        List<DatadictPo> poList = datadictService.queryList(condition);
        DatadictPo po = new DatadictPo();
        if (poList != null && poList.size() == 0) {
            po = poList.get(0);
        }
        DatadictVo vo = CopyUtil.transfer(po, DatadictVo.class);
        return getSuccessResult(vo);
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "查询弱密码数量", notes = "查询弱密码数量", httpMethod = "GET")
    @Loggable(descp = "查询弱密码数量", type = LogTypeEnum.QUERY, include = "")
    @RequestMapping(value = "/queryCount", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<Integer> queryCount(@ModelAttribute @Valid WeakPwdQueryForm form)
            throws SystemServiceException {
        DatadictCondition condition = this.getConditionByQueryForm(form);
        condition.setDataDictTypeCode(Constants.WEAK_DICT_TYPE);
        condition.setDelFlag(Constants.NOT_DELETED);
        int count = datadictService.queryCount(condition);
        return getSuccessResult(count);
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "查询弱密码列表", notes = "查询弱密码列表", httpMethod = "GET")
    @Loggable(descp = "查询弱密码列表", type = LogTypeEnum.QUERY, include = "")
    @RequestMapping(value = "/queryList", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<CentreListResponse<DatadictVo>> queryList(@ModelAttribute @Valid WeakPwdQueryForm form)
            throws SystemServiceException {
        DatadictCondition condition = this.getConditionByQueryForm(form);
        condition.setDelFlag(Constants.NOT_DELETED);
        condition.setDataDictTypeCode(Constants.WEAK_DICT_TYPE);
        List<DatadictPo> poList = datadictService.queryList(condition);
        List<DatadictVo> voList = CopyUtil.transfer(poList, DatadictVo.class);
        return getSuccessResult(getListResponse(voList));
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "查询弱密码列表(带分页)", notes = "查询弱密码列表(带分页)", httpMethod = "GET")
    @Loggable(descp = "查询弱密码列表(带分页)", type = LogTypeEnum.QUERY, include = "")
    @RequestMapping(value = "/queryPageList", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity<CentreCutPageResponse<DatadictVo>> queryPageList(@ModelAttribute @Valid WeakPwdQueryForm form)
            throws SystemServiceException {
        DatadictCondition condition = this.getConditionByQueryForm(form);
        condition.setDelFlag(Constants.NOT_DELETED);
        condition.setDataDictTypeCode(Constants.WEAK_DICT_TYPE);
        List<DatadictVo> voList = new ArrayList<>();
        int count = datadictService.queryCount(condition);
        if (count > 0) {
            List<DatadictPo> poList = datadictService.queryList(condition);
            voList = CopyUtil.transfer(poList, DatadictVo.class);
        }
        return getSuccessResult(getPageResponse(form, count, voList));
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "修改弱密码", notes = "修改弱密码", httpMethod = "POST")
    @Loggable(descp = "修改弱密码", type = LogTypeEnum.UPDATE, include = "")
    @RequestMapping(value = "/update", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity update(@ModelAttribute @Valid WeakPwdUpdateForm form)
            throws SystemServiceException {
        DatadictPo po = CopyUtil.transfer(form, DatadictPo.class);
        po.setDataDictTypeCode(Constants.WEAK_DICT_TYPE);
        po.setRestartEffect(0);
        po.setDelFlag(Constants.NOT_DELETED);
        DatadictCondition condition = CopyUtil.transfer(po, DatadictCondition.class);
        int count = weakPwdService.selectByvalue(condition);
        if (count != Constants.WEAKPWDREPEAT) {
            logger.error("已经存在相同的弱密码值,新增弱密码失败");
            return getFailResult("已经存在相同的弱密码值");
        }
        datadictService.update(po);
        return getSuccessResult();
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "删除弱密码", notes = "删除弱密码", httpMethod = "POST")
    @Loggable(descp = "删除弱密码", type = LogTypeEnum.DELETE, include = "")
    @RequestMapping(value = "/delete", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity delete(@Valid @RequestParam(value = "id") List<Integer> id) throws SystemServiceException {
        if (id == null || id.size() == 0) {
            return getFailResult("参数错误");
        } else {
            return batchDelete(id);
        }
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "批量删除弱密码", notes = "批量删除弱密码", httpMethod = "POST")
    @Loggable(descp = "批量删除弱密码", type = LogTypeEnum.DELETE, include = "")
    @RequestMapping(value = "/batchDelete", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity batchDelete(
            @ApiParam(value = "字典ID", required = true) @RequestParam List<Integer> dataDictIdList)
            throws SystemServiceException {
        datadictService.batchDelete(dataDictIdList);
        return getSuccessResult();
    }

    @NeedRole("sysadminrole")
    @ApiOperation(value = "导入弱密码", notes = "导入弱密码", httpMethod = "POST")
    @Loggable(descp = "导入弱密码", type = LogTypeEnum.IMPORT, include = "")
    @RequestMapping(value = "/import", method = {RequestMethod.GET, RequestMethod.POST})
    public ResponseEntity importUserLog(@RequestParam("file") MultipartFile file) {
        return getFailResult("暂不支持导入弱密码功能");
    }

    private boolean checkElseCreate(String path) {
        boolean result = false;
        if (StringUtils.isBlank(path)) {
            return result;
        }
        if (!new File(path).exists()) {
            result = new File(path).mkdirs();
        } else {
            result = true;
        }
        return result;
    }

    /**
     * excel数据转换成对象
     *
     * @param sheet 表格数据
     * @return
     */
    private List<DatadictPo> transToWeakPwd(List<List<String>> sheet) {
        List<DatadictPo> datas = new ArrayList<>();
        int index = 0;
        for (List<String> data : sheet) {
            index++;
            if (index == 1) {
                continue;
            }
            DatadictPo po = new DatadictPo();
            // 字典值
            if (StringUtils.isBlank(data.get(0))) {
                continue;
            }
            po.setDataDictValue(data.get(0));
            // 备注
            if (data.size() > 1 && StringUtils.isNotBlank(data.get(1))) {
                po.setRemark(data.get(1));
            }
            datas.add(po);
        }
        return datas;
    }

    /**
     * 下载文件
     *
     * @return BusinessServiceException
     */
    @Loggable(descp = "下载导入模板文件", type = LogTypeEnum.DOWNLOAD, include = "")
    @ApiOperation(value = "下载导入模板文件", notes = "下载导入模板文件", httpMethod = "GET")
    @RequestMapping(value = "/download", method = {RequestMethod.GET, RequestMethod.POST})
    public void download(HttpServletRequest request, HttpServletResponse response)
            throws IOException {
        FileInputStream fis = null;
        ServletOutputStream out = null;
        try {
            Resource resource = new ClassPathResource("弱密码导入表.xlsx");
            fis = new FileInputStream(resource.getFile());
            // 解决中文文件名下载后乱码的问题
            String fileName = URLEncoder.encode("弱密码导入表.xlsx", "utf-8");
            out = response.getOutputStream();
            response.setCharacterEncoding("utf-8");
            response.setContentType("application/octet-stream");
            response.setContentLength(fis.available());
            response.setHeader("Content-Disposition", "attachment; filename=" + fileName + "");
            byte[] b = new byte[4096];
            while (fis.read(b) > 0) {
                out.write(b);
            }
            fis.close();
            // 获取响应报文输出流对象
            out.flush();
            out.close();
        } catch (Exception e) {
            logger.error("OnlineEdit download file occured error", e);
        } finally {
            if (fis != null) {
                fis.close();
            }
            if (out != null) {
                out.close();
            }
        }
    }

    /**
     * DatadictQueryForm转换为DatadictCondition
     *
     * @param form
     * @return
     */
    private DatadictCondition getConditionByQueryForm(WeakPwdQueryForm form) {
        DatadictCondition condition = CopyUtil.transfer(form, DatadictCondition.class);
        return condition;
    }
}
